package activiti;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.activiti.engine.HistoryService;
import org.activiti.engine.ProcessEngine;
import org.activiti.engine.ProcessEngines;
import org.activiti.engine.RepositoryService;
import org.activiti.engine.RuntimeService;
import org.activiti.engine.TaskService;
import org.activiti.engine.history.HistoricTaskInstance;
import org.activiti.engine.repository.Deployment;
import org.activiti.engine.repository.ProcessDefinition;
import org.activiti.engine.repository.ProcessDefinitionQuery;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.TaskQuery;
import org.junit.Test;

public class ActivitiDemo {
	// 部署流程
	@Test
	public void deploy() {
		// 获取流程引擎
		ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
		// 获取仓库服务的实例
		Deployment deployment = engine.getRepositoryService().createDeployment()
				.addClasspathResource("diagrams/MyProcess.bpmn").addClasspathResource("diagrams/MyProcess.png")
				.deploy();
		System.out.println(deployment.getId() + "--->" + deployment.getName());
	}

	// 查询流程
	@Test
	public void startProcess() {
		ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
		RepositoryService repositoryService = engine.getRepositoryService();
		// 创建流程定义查询对象
		ProcessDefinitionQuery definitionQuery = repositoryService.createProcessDefinitionQuery();

		String processDefinitionKey = "myProcess";
		// 设置流程定义的key的查询条件
		definitionQuery.processDefinitionKey(processDefinitionKey);
		// 查询所有的流程定义
		List<ProcessDefinition> processDefinitionList = definitionQuery.list();
		for (ProcessDefinition definition : processDefinitionList) {
			System.out.println("-------------------------");
			System.out.println("流程定义id:" + definition.getId());
			System.out.println("流程资源名：" + definition.getResourceName());
			System.out.println("流程部署id:" + definition.getDeploymentId());
		}
	}

	// 启动一个流程实例
	@Test
	public void startProcessInstance() {
		ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
		RuntimeService runtimeService = engine.getRuntimeService();

		String processDefinitionKey = "myProcess:5:35004";
		// 根据流程定义的key启动一个流程实例
		ProcessInstance processInstance = runtimeService.startProcessInstanceById(processDefinitionKey);
		System.out.println("流程实例id:" + processInstance.getId());
		System.out.println("流程定义id:" + processInstance.getProcessDefinitionId());
 
	}
	//查询当前用户的代办任务
    @Test
    public void queryProcessInstance(){
        ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
        //查询任务使用的service
        TaskService taskService = engine.getTaskService();
        //获取任务查询对象
        TaskQuery taskQuery = taskService.createTaskQuery();
        taskQuery.taskAssignee("xiaoxia");
        //查询该条件下的所有的任务
        List<org.activiti.engine.task.Task> tasks =taskQuery.list();
        for(org.activiti.engine.task.Task task:tasks){
            System.out.println("当前任务id:"+task.getId());
            System.out.println("当前任务所属流程定义id:"+task.getProcessDefinitionId());
            System.out.println("当前任务的key:"+task.getTaskDefinitionKey());
        }
        
    }
	//处理人处理任务
    @Test
    public void handlerTask() {
    	//任务id，后期整合后会通过当前登录人的身份查询到该用户的任务，然后获取该id
    	String taskId = "40002";
    	ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
    	TaskService service = engine.getTaskService();
    	//根据id完成该任务
    	service.complete(taskId);
    }
    
    //查看流程附件(图片)
    @Test
    public void viewImage() throws IOException {
    	String id = "5001";
    	ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
    	//在仓库中根据部署id获得流程图片的文件名
    	RepositoryService service = engine.getRepositoryService();
    	List<String> list =  service.getDeploymentResourceNames(id);
    	if(list==null) {
    		System.out.println("没有该流程");
    	}
    	//文件名
    	String imageName = null;
    	for(String str:list) {
    		Integer a = new Integer(1);
    		if(str.indexOf(".png")>=0) {
    			imageName = str;
    			System.out.println(imageName);
    		}
    	}
    	File file = new File("d:/"+imageName);
    	System.out.println( file.getPath());
    	if(!file.exists()) {
    		file.mkdirs();
    		file.createNewFile();
    	}
    	InputStream in = service.getResourceAsStream(id,imageName);
    	FileOutputStream fileout = new FileOutputStream(file);
    	int len = 0;
    	byte[] databyte = new byte[1024];
    	while((len=in.read(databyte))!=-1) {
    		fileout.write(databyte, 0, len);
    	}
    	System.out.println("文件下载完毕");
    }
    
    //查询历史流程实例
    @Test
    public void queryHistoryTask() {
    	ProcessEngine engine = ProcessEngines.getDefaultProcessEngine();
    	HistoryService service = engine.getHistoryService();
    	List<HistoricTaskInstance> list = service.createHistoricTaskInstanceQuery().taskAssignee("xiaoxia").list();
    	  if(list!=null && list.size()>0){
              for(HistoricTaskInstance hti:list){
                  System.out.println(hti.getId()+"    "+hti.getName()+"    "+hti.getProcessInstanceId()+"   "+hti.getStartTime()+"   "+hti.getEndTime()+"   "+hti.getDurationInMillis()+hti.getAssignee());
              }
          }
    }
    
    //设置流程变量
    @Test
    public void setProcessVariable() {
    	//装备好数据
    	Map<String,Object> map = new HashMap<String,Object>();
    	map.put("请假人", "小夏");
    	map.put("请假原因", "拉屎");
    	//获取执行的service
        RuntimeService service = ProcessEngines.getDefaultProcessEngine().getRuntimeService();
        ProcessInstance instance = service.startProcessInstanceById("myProcess:5:35004",map);
        System.out.println("流程启动完成,id为:"+instance.getId());
    }
   
    //查询设置的流程变量
    @Test
    public void searchVariable() {
    	RuntimeService service = ProcessEngines.getDefaultProcessEngine().getRuntimeService();
    	String name = (String)service.getVariable("45001", "请假人");
    	String reason = (String)service.getVariable("45001", "请假原因");
    	System.out.println("请假人是:"+name+"请假原因:"+reason);
    }
    
}
